# Author: didiplus
# Date: 2025-01-22 15:49:54
# LastEditTime: 2025-01-22 15:49:57
# LastEditors: didiplus
# Description: 算术验证码类
# FilePath: \pythonscript\Captcha\utls\ArithmeticCaptcha.py

from .CaptchaBase import CaptchaBase
import random
from PIL import Image, ImageDraw

class ArithmeticCaptcha(CaptchaBase):
    """算术验证码"""  

    def generate(self):
        """生成算术验证码"""
        operators = {"+": lambda x, y: x + y, "-": lambda x, y: x - y, "x": lambda x, y: x * y}
        self.expression = []
        for i in range(self.length):
            self.expression.append(str(random.randint(1, 9)))
            if i < self.length - 1:
                self.expression.append(random.choice(list(operators.keys())))

        # 计算表达式结果时将 'x' 替换为 '*'
        eval_expression = [char if char != 'x' else '*' for char in self.expression]
        self.chars = str(eval("".join(eval_expression)))  # 计算表达式结果

        # 将表达式转换为字符串形式，用于显示
        self.expression = "".join(self.expression) + "=?"

    def create_image(self) -> Image.Image:
        """生成算术验证码图像"""
        if self.chars is None:
            self.generate()
        image = Image.new("RGB", (self.width, self.height), (255, 255, 255))
        draw = ImageDraw.Draw(image)

        if self.font is None:
            self.set_font()

        # 动态调整字体大小以适应图片高度
        max_font_size = self.height - 10  # 预留 10 像素的上下边距
        if self.font.size > max_font_size:
            self.set_font(self.font.path, max_font_size)

        # 计算所有字符的总宽度
        total_width = 0
        for char in self.expression:
            bbox = draw.textbbox((0, 0), char, font=self.font)
            char_width = bbox[2] - bbox[0]
            total_width += char_width

        # 动态计算间距比例，基于字体大小调整
        base_spacing = max(5, self.font.size // 5)  # 增加间距比例
        total_width += base_spacing * (len(self.expression) - 1)

        # 计算起始位置以使字符居中
        x_start = (self.width - total_width) // 2

        # 绘制每个字符
        for char in self.expression:  # 假设 expression 是需要显示的文本
            try:
                color = self.random_color()  # 每个字符随机一个颜色
                draw.text((x_start, self.height // 4), char, font=self.font, fill=color)

                # 获取字符宽度
                bbox = draw.textbbox((0, 0), char, font=self.font)
                char_width = bbox[2] - bbox[0]
                # 更新 x 坐标
                x_start += char_width + base_spacing
            except OSError:
                print(f"字体不支持字符: {char}")
                continue
        self.draw_hollow_circle(draw, num_circles=10)
        self.draw_bezier_curve(draw, num_curves=2)
        return image